package org.halk.aspect;

import lombok.extern.slf4j.Slf4j;

import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.Semaphore;

/**
 * 内存实现
 *
 * @Author halk
 * @Date 2024/9/19 16:02
 **/
@Slf4j
//@Component
public class LockMemoryServiceImpl implements LockService {

    //多线程安全的设计
    private static final ConcurrentHashMap<String, Semaphore> LOCK_MAP = new ConcurrentHashMap<>();
    //定时任务判断key是否过期
    private static final Map<String, Long> scheduleMap = new HashMap<>();
    private static final Timer timer = new Timer();

    //循环判断key是否过期
    static {
        timer.schedule(new TimerTask() {
            @Override
            public void run() {
                Iterator<Map.Entry<String, Long>> iterator = scheduleMap.entrySet().iterator();
                while (iterator.hasNext()) {
                    Map.Entry<String, Long> entry = iterator.next();
                    if (System.currentTimeMillis() > entry.getValue()) {
                        Semaphore semaphore = LOCK_MAP.get(entry.getKey());
                        if (semaphore != null) {
                            semaphore.release();
                        }
                        LOCK_MAP.remove(entry.getKey());
                        iterator.remove();
                    }
                }
            }
        }, 0, 50L);
    }


    @Override
    public Boolean lock(String key, long expireTime) {
        Semaphore semaphore = LOCK_MAP.computeIfAbsent(key, k -> new Semaphore(1));
        if (semaphore.tryAcquire()) {
            scheduleMap.put(key, System.currentTimeMillis() + expireTime);
            return true;
        } else {
            return false;
        }
    }

    @Override
    public Boolean unLock(String key) {
        Semaphore semaphore = LOCK_MAP.get(key);
        if (semaphore != null) {
            LOCK_MAP.remove(key);
            semaphore.release();
        }
        return true;
    }

}
